<template>
    <div class="table">
        <div class="dataTable">
            <el-table
                    id="zTable"
                    ref="multipleTable"
                    v-loading="options.loading"
                    :data="list"
                    :stripe="options.stripe"
                    :border="options.border"
                    :default-sort="options.defaultSort||{prop: 'id',order: 'descending'}"
                    @row-click="rowClick"
                    @sort-change='sortChange'
                    @selection-change="handleSelectionChange">
                <!--region 选择框-->
                <el-table-column v-if="options.multipleSelect" type="selection" style="width: 55px;">
                </el-table-column>
                <!--endregion-->
                <!--region 数据列-->
                <template v-for="(column, index) in columns">
                    <el-table-column :prop="column.prop"
                                     :label="column.label"
                                     :align="column.align"
                                     :sortable="column.sortable"
                                     :show-overflow-tooltip="column.showOverflowTooltip"
                                     :width="column.width">
                        <template slot-scope="scope">
                            <template v-if="!column.render">
                                <template v-if="column.formatter">
                                    <span v-html="column.formatter(scope.row, column)"/>
                                </template>
                                <template v-else>
                                    <span>{{scope.row[column.prop]}}</span>
                                </template>
                            </template>
                            <template v-else>
                                <expand-dom :column="column" :row="scope.row" :render="column.render"
                                            :index="index"/>
                            </template>
                        </template>
                    </el-table-column>
                </template>
                <!--endregion-->
                <!--region 按钮操作组-->
                <el-table-column :label="operates.title===undefined?'操作':operates.title" align="center"
                                 :width="(operates.width===undefined||operates.width==='auto')?operates.list.length*100:operates.width"
                                 :fixed="(device==='desktop')&&(operates.fixed===undefined?'right':operates.fixed)"
                                 v-if="(operates.list.length > 0)"
                >
                    <template slot-scope="scope">
                        <div>
                            <template v-for="(btn, key) in operates.list">
                                <el-button :type="btn.type" size="mini" :icon="btn.icon"
                                           v-permission="btn.permission"
                                           :disabled="btn.disabled(scope.$index,scope.row)"
                                           :plain="btn.plain" @click.native.prevent="btn.method(key,scope.row)">{{
                                    btn.label }}
                                </el-button>
                            </template>
                        </div>
                    </template>
                </el-table-column>
                <!--endregion-->
            </el-table>
        </div>
        <!--region 分页-->
        <el-pagination class="pageRow" :style="{'text-align': device==='mobile'?'center':'right'}" v-if="pagination" @size-change="handleSizeChange"
                       @current-change="handleIndexChange"
                       :page-size="pagination.pageSize"
                       :small="device==='mobile'"
                       :page-sizes="pagination.pageArray" :current-page="pagination.pageNum"
                       :layout="device==='mobile'?'prev, pager, next, jumper':'total,sizes, prev, pager, next, jumper'"
                       :hide-on-single-page="pagination.total<=10"
                       :total="pagination.total"/>
    </div>
</template>
<script lang="ts">
    import {Component, Prop, Vue} from "vue-property-decorator";
    import {Getter} from "vuex-class";

    @Component({
        components: {
            expandDom: {
                functional: true,
                props: {
                    row: Object,
                    render: Function,
                    index: Number,
                    column: {
                        type: Object,
                        default: null
                    }
                },
                render: (createElement: any, context: any) => {
                    //详细使用方法见 https://cn.vuejs.org/v2/guide/render-function.html#createElement-%E5%8F%82%E6%95%B0
                    const params = {
                        row: context.props.row,
                        index: context.props.index,
                        column: ""
                    };
                    if (context.props.column) {
                        params.column = context.props.column;
                    }
                    return context.props.render(createElement, params);
                }
            }
        }
    })
    export default class DataTable extends Vue {
        @Prop() private api!: Function;
        @Prop() private columns!: Array<any>;// 需要展示的列 === prop：列数据对应的属性，label：列名，align：对齐方式，width：列宽,showOverflowTooltip:隐藏多余字符
        @Prop() private operates!: any;// width:按钮列宽，fixed：是否固定（left,right）,按钮集合 === label: 文本，type :类型（primary / success / warning / danger / info / text），show：是否显示，icon：按钮图标，plain：是否朴素按钮，disabled：是否禁用，method：回调方法
        @Prop({
            default: () => ({//分页参数
                pageNum: 1,
                pageSize: 10,
                pageArray: [10, 30, 50, 100],
                total: 0
            })
        }) private pagination!: any;
        @Prop({
            default: () => ({//表格样式参数
                stripe: false, // 是否为斑马纹 table
                loading: false, // 是否添加表格loading加载动画
                highlightCurrentRow: false, // 是否支持当前行高亮显示
                multipleSelect: false, // 是否支持列表项选中功能
                defaultSort: {
                    prop: "id",
                    order: "descending"
                },
                border: false
            })
        }) private options!: any;

        @Prop() private query: any;//查询参数
        @Getter("device") private device!: string;
        private list: Array<any> = [];
        private multipleSelection: Array<any> = [];// 多行选中

        /* created() {
             this.change();
         }*/

        // 切换每页显示的数量
        handleSizeChange(size: number) {
            if (this.pagination) {
                this.pagination.pageNum = 1;
                this.pagination.pageSize = size;
                this.change();
            }
        }

        // 切换页码
        handleIndexChange(pageNum: number) {
            if (this.pagination) {
                this.pagination.pageNum = pageNum;
                this.change();
            }
        }

        sortChange(column: any, prop: any, order: any) {
            if (column) {
                this.pagination.orderByColumn = column.prop;
                if (column.order === "descending") {
                    this.pagination.isAsc = "desc";
                } else if (column.order === "ascending") {
                    this.pagination.isAsc = "asc";
                } else {
                    delete this.pagination["isAsc"];
                }
            } else {
                delete this.pagination["orderByColumn"];
                delete this.pagination["isAsc"];
            }
            this.change();
        }

        change() {
            this.refresh();
            this.$emit("update:pagination", this.pagination);
        }

        // 多行选中
        handleSelectionChange(val: any) {
            this.multipleSelection = val;
            this.$emit("handleSelectionChange", val);
        }

        rowClick(val: any) {
            // this.toggleSelection(val);
            this.$emit("rowClick", val);
        }

        toggleSelection(row: any) {
            if (row) {
                (this.$refs.multipleTable as any).toggleRowSelection(row);
            } else {
                (this.$refs.multipleTable as any).clearSelection();
            }
        }

        handleParams() {
            let options = this.query || {};
            if (this.pagination) {
                options.pageNum = this.pagination.pageNum;
                options.pageSize = this.pagination.pageSize;
                options.orderByColumn = this.pagination.orderByColumn;
                options.isAsc = this.pagination.isAsc;
            }
            if (!options.orderByColumn) {
                options.orderByColumn = "id";
            }
            if (!options.isAsc) {
                options.isAsc = "desc";
            }
            return options;
        }

        refreshData(api: any) {
            api(this.handleParams()).then((res: any) => {
                if (res.rows && res.rows.length === 0 && res.total !== 0) {//如果当前页数据为空，并且总条数大于0，那么改变页码，刷新数据
                    this.pagination.pageNum = this.pagination.pageNum - 1;
                    this.refresh();
                }
                this.list = res.rows;
                this.pagination.total = res.total;
                this.$emit("handleEvent", "list", res);
            }).catch((e) => {
                console.log(e);
            });
        }

        mounted() {

        }

        refresh() {
            this.refreshData(this.api);
        }

        activated() {
            this.refreshData(this.api);
        }
    }
</script>

<style scoped lang="scss">
    .table {
        width: calc(100%);

        .dataTable {
            flex: 1;
        }


        .pageRow {
            margin: 10px;
            overflow: hidden;
        }
    }
</style>

